package org.light4admin.util;


import lombok.extern.slf4j.Slf4j;
import org.light4admin.common.base.BusinessException;
import org.light4admin.common.base.Response;
import org.light4admin.common.base.ResponseCode;
import org.springframework.util.CollectionUtils;

import javax.validation.ConstraintViolation;
import javax.validation.Validation;
import javax.validation.Validator;
import javax.validation.ValidatorFactory;
import java.util.Objects;
import java.util.Set;

/**
 * 参数校验工具类
 *
 * @author light4admin
 * @date:2018/9/5
 */
@Slf4j
public class ValidateUtil {

    private static Validator validator;

    static {
        ValidatorFactory factory = Validation.buildDefaultValidatorFactory();
        validator = factory.getValidator();
    }

    private ValidateUtil() {

    }

    /**
     * 校验bean入参合法性
     *
     * @param bean 入参
     * @param <T>
     * @return
     */
    public static <T> Response<Void> validate(T bean) {
        if (Objects.isNull(bean)) {
            log.warn("[validate]非法入参,bean=[{}]", bean);
            throw new BusinessException(ResponseCode.PARAM_ILLEGAL);
        }
        Response<Void> response = validateNonThrowExceiption(bean);
        if (Response.isSuccess(response)) {
            return response;
        } else {
            log.warn("[validate]非法入参,bean=[{}],error=[{}]", bean, response.toString());
            throw new BusinessException(ResponseCode.PARAM_ILLEGAL, response.toString());
        }
    }

    /**
     * 校验bean入参合法性
     * （不抛异常）
     *
     * @param <T>
     * @param bean
     * @return
     */
    public static <T> Response<Void> validateNonThrowExceiption(T bean) {
        Set<ConstraintViolation<T>> violations = validator.validate(bean);
        StringBuilder errMsg = new StringBuilder();
        if (!CollectionUtils.isEmpty(violations)) {
            for (ConstraintViolation<T> violation : violations) {
                errMsg.append(violation.getPropertyPath().toString())
                        .append(" ")
                        .append(violation.getMessage())
                        .append("; ")
                        .append(violation.getInvalidValue() == null ? "" : violation.getInvalidValue().toString());
            }

            if (!violations.isEmpty()) {
                log.warn("validate result message: {}", errMsg);
                return Response.failed(errMsg.toString());
            }
        }
        return Response.success();
    }

}
